home *** CD-ROM | disk | FTP | other *** search
/ Amiga Game-Power / Amiga Game-Power.iso / power games ii / galactic worm / corewars / anleitung / kapiteli < prev    next >
Text File  |  1994-05-20  |  70KB  |  1,512 lines

  1.  
  2.                          Kapitel 1: Das Spiel
  3.                          ____________________
  4.  
  5.  
  6.  
  7.  
  8. 1.1 Einleitung
  9. ______________
  10.  
  11.  
  12. Wohl Niemand könnte das Prinzip des vorliegenden Computerspiels besser
  13. in Worte fassen als sein Erfinder, A. K. Dewdney:
  14.  
  15.   "Zwei Computerprogramme in ihrer natürlichen Umgebung - dem Speicherchip
  16.    eines Computers - beschleichen einander von Adresse zu Adresse. 
  17.    Manchmal sind sie darauf aus, den Gegner auszukundschaften.  Manchmal
  18.    legen sie einen Sperrgürtel aus numerischen Bomben, und manchmal
  19.    kopieren sie sich selbst aus der Gafahrenzone oder halten inne, um
  20.    Schäden zu beheben.  Das ist das Spiel, das ich "Krieg der Sterne"
  21.    nennen möchte.  Es ist ganz anders als die meisten anderen  
  22.    Computerspiele, denn Menschen spielen hier überhaupt nicht mehr mit. 
  23.    Zwar sind die rivalisierenden Programme natürlich von irgendwem
  24.    geschrieben; aber sobald der Kampf einmal tobt, kann der Erfinder eines
  25.    Programmes nur mehr hilflos abwarten, ob das Produkt stundenlangen
  26.    überlegens und Programmierens siegt oder untergeht.  Den Ausgang der
  27.    Schlacht entscheidet allein, welches Programm an einer empfindlichen
  28.    Stelle getroffen wird. "
  29.  
  30.    (Zitat aus: Artikel "Computer Kurzweil", Spektrum der Wissenschaft, 
  31.    August 1984, von A. K. Dewdney)
  32.  
  33.  
  34.  
  35.  
  36. 1.2 Einige Begriffe
  37. ___________________
  38.  
  39.  
  40. Im Verlauf dieser Anleitung werden wir wiederholt einige
  41. Fachbegriffe verwenden, um etwas zu erklären.  Es wäre zwar an einigen
  42. Stellen möglich gewesen, die englischen Wörter durch deutsche Synonyme
  43. zu ersetzen, doch Sie werden sehen, dass eine Bezeichnung wie
  44. "Assembler" (von englisch to assemble, = montieren) nach kurzer Zeit
  45. weniger verwirrend ist als das deutsche Wort "Uebersetzer".  Sie finden
  46. übrigens im Anhang B der Anleitung eine alphabetisch geordnete
  47. Aufstellung der im Text verwendeten Fachbegriffe. 
  48.  
  49.  
  50. 1.2.1 Programm
  51. --------------
  52.  
  53. Ein Programm ist eine Folge von Anweisungen, die einem
  54. beliebigen ausführenden Objekt eine bestimmte Handlungsweise
  55. vorschreiben.  Ein Fernsehprogramm ist daher im Prinzip das gleiche wie
  56. ein Programm einer Waschmaschine oder eines Computers.  Der grösste
  57. Unterschied dieser drei Beispiele besteht in der Art und Weise der
  58. Formulierung des Programmes.  Das Fernsehprogramm ist durch Zeitangaben
  59. und Namen der Sendungen, die zu diesen Zeiten ausgestrahlt werden,
  60. formuliert. 
  61.  
  62. Das Programm einer älteren Waschmaschine ist durch die Form der
  63. Steuerscheibe bestimmt, einer Metallscheibe, die an bestimmten Stellen
  64. Einbuchtungen oder Erhebungen besitzt und die sich langsam um die eigene
  65. Achse dreht.  Ein Fühler berührt den Rand der Scheibe und löst je nach
  66. dem augenblicklichen Stand der Scheibe bestimmte Kontake aus, die z.B. 
  67. Wasser einlassen oder die Trommel in Bewegung setzen.  Bei einer
  68. moderneren Maschine übernimmt bereits ein Computer die Aufgabe der
  69. Steuerscheibe. 
  70.  
  71. Somit wären wir beim dritten Beispiel angelangt, beim Computer. 
  72. Sehen wir uns als erstes ein Textverarbeitungsprogramm an.  Es besteht
  73. aus nichts anderem als Anweisungen in einer besonderen, dem Computer
  74. verständlichen Sprache.  Duch diese Sprache weiss der Computer immer,
  75. was er als nächstes tun soll: Eingaben von der Tastatur annehmen, einen
  76. Text ausdrucken, auf eine bestimmte Aktion des Benutzers einen
  77. Buchstaben des Textes löschen.  Der grosse Vorteil des Computers
  78. gegenüber einer alten Waschmaschine, die durch die Steuerkurve
  79. "programmiert" wurde, ist nun, dass anstelle eines
  80. Textverarbeitungsprogrammes genausogut ein beliebiges anderes Programm
  81. hätte laufen können.  Man sagt, der Computer sei "frei programmierbar". 
  82.  
  83.  
  84. 1.2.2 Hardware und Software
  85. ---------------------------
  86.  
  87. Dies sind die Bezeichnungen für einen Computer, auf dem ein
  88. Programm laufen kann und für das Programm, das auf dem Computer oder
  89. eben der Hardware läuft.  Software kann aber auch aus Text oder aus
  90. Daten für eine Datenbank bestehen.  Generell kann man beliebige
  91. Informationen als Software bezeichnen.  Genauso gilt als Hardware nicht
  92. nur ein Computer, sondern auch die Zusatzgeräte rund um einen Computer,
  93. wie Diskettenlaufwerke, Monitoren, oder Speicherkarten. 
  94.  
  95.  
  96. 1.2.3 Programmiersprache
  97. ------------------------
  98.  
  99. Eine Programmiersprache ist die Art und Weise, einem Computer
  100. eine Folge von Anweisungen beizubringen.  Diese Sprachen können entweder
  101. nur aus Zahlen oder aus einer Mischung von verständlichen Wörtern und
  102. Zahlen bestehen.  Man unterscheidet hier vor allem zwischen zwei
  103. verschiedenen Sprachgruppen: Maschinensprachen und Hochsprachen.  Eine
  104. Hochsprache ist auf den Menschen zugeschnitten und daher leichter zu
  105. lernen und zu bedienen.  Eine Maschinensprache ist hingegen auf einen
  106. Computer zugeschnitten, und das bedingt die Anpassung des Menschen an
  107. die Maschine.  Maschinensprache ist schnell, aber schwieriger zu
  108. erlernen. Grosse Softwareprojekte werden in der Regel in Hochsprachen
  109. erstellt. 
  110.  
  111.  
  112. 1.2.4 Interpreter
  113. -----------------
  114.  
  115. Ein Interpreter liest jeweils aus einem Programm in der Hochsprache den
  116. nächsten einzelnen Befehl, übersetzt ihn in die Maschinensprache und
  117. führt diese dann aus.  Wenn in einem Programm ein solcher Befehl
  118. mehrmals vorkommt, muss er jedesmal neu übersetzt werden, was
  119. natürlich viel Zeit kostet.  Basic ist das Standardbeispiel für eine
  120. Sprache, die während der Ausführung übersetzt wird, und deshalb im
  121. Vergleich mit Compilersprachen sehr langsam ist.  Weil zudem eine
  122. Anweisung in einer Hochsprache in mehrere Maschinensprachebefehle
  123. übersetzt werden muss, verstärkt sich die Verlangsmung der
  124. Interpretersprachen zusätzlich. 
  125.  
  126.  
  127. 1.2.5 Compiler
  128. --------------
  129.  
  130. Der Compiler dagegen nimmt sich gleich zu Beginn das ganze
  131. Programm in der Hochsprache vor und übersetzt es in ein vollständiges
  132. Maschinenspracheprogramm.  Er montiert sozusagen die einzelnen Befehle
  133. des Programmes zu einem grossen, dem Computer verständl ichen
  134. Maschinenspracheprogramm, das später in einem Stück läuft. 
  135.  
  136. Pascal oder C sind Beispiele für Sprachen, die vor dem Starten des
  137. Programmes zuerst vollständig in den Maschinencode übersetzt und
  138. erst dann vom Computer ausgeführt werden.  Das bringt zwar schnelle
  139. Programme, auf der anderen Seite jedoch eine langwierige Fehlersuche. 
  140. Wenn auch nur eine winzige Kleinigkeit eines solchen Programmes
  141. geändert werden soll, muss der Programmtext nach der Korrektur ganz
  142. oder teilweise neu übersetzt (= compiliert) werden.
  143.  
  144.  
  145. 1.2.6 Terminal
  146. --------------
  147.  
  148. Es handelt sich hier um einen Sammelbegriff für Geräte, die die
  149. Kommunikation zwischen Computer und Mensch möglich machen.  Ein Terminal
  150. kann ein Monitor, ein Drucker oder eine Tastatur sein, aber auch ein
  151. Computer, der die Ein- und Ausgaben für ein gröss eres, vernetztes
  152. (zusammengeschaltetes) Computersystem übernimmt, sein. 
  153.  
  154.  
  155. 1.2.7  Bit und Byte
  156. -------------------
  157.  
  158. Ein Bit ist die kleinste Speichereinheit eines Computers.  Ein
  159. solches Bit kann nur zwei Zustände annehmen: 0 oder 1.  In der
  160. Computertechnologie werden 8 dieser Bits zu einem Byte zusammengefasst. 
  161. Diese 8 Bits können dann als Ganzes insgesamt 256 verschiedene Zustände
  162. annehmen.  Diese Zustände werden durch die Zahlen von 0 bis 255
  163. beschrieben. 
  164.  
  165. Der gesamte Speicher eines Computers besteht ausschliesslich aus
  166. sehr vielen einzelnen Bytes.  Die Bytes werden von 0 beginnend
  167. durchnummeriert, das heisst, jedem einzelnen Byte im Speicher wird eine
  168. eigene Nummer oder Adresse zugewiesen.  So kann auf ein beliebiges Byte
  169. im Speicher durch seine Adresse zugegriffen werden. 
  170.  
  171. Wenn man über Computer spricht, werden unweigerlich die Begriffe KByte
  172. oder MByte fallen.  Ein KByte ist ganz einfach ein 'Kilobyte' (wird auch
  173. so ausgesprochen) und bedeutet 1024 Bytes.  Ein MByte ist
  174. dementsprechend ein 'Megabyte' und umfasst 1024 mal 1024 Bytes, also
  175. 1'048'576 Bytes.  Die Gross- und Kleinschreibung bei diesen Begriffen
  176. muss beachtet werden: Ein kByte und ein mByte sind im Gegensatz zum
  177. KByte und zum MByte nur 1000, bzw.  1000000 Bytes gross. 
  178.  
  179.  
  180. 1.2.8 Assembler
  181. ---------------
  182.  
  183. Ein Assembler ist ein Programm, das einen Programmtext, der in
  184. einer Assemblersprache geschrieben wurde, in den ausführbaren
  185. Maschinencode übersetzt.  Im Prinzip ist eine Assemblersprache und
  186. Maschinensprache genau dasselbe, der Unterschied besteht einzig
  187. und allein darin, dass eine Assemblersprache die Befehle der
  188. Maschinensprache anstatt in Zahlen in Buchstaben akzeptiert.  Für jeden
  189. Befehl in Maschinensprache steht ein Wort, das die Bedeutung des Befehls
  190. ungefähr umschreibt.  Da man sich Wörter viel leichter merken kann als
  191. nackte Zahlen, wird Maschinensprache heutzutage vorwiegend mit Hilfe
  192. eines Assemblers programmiert.  Es ist wichtig, dass man den Unterschied
  193. zwischen einem Assembler und einer Assemblersprache kennt: Der Assembler
  194. übersetzt die Assemblersprache in den entsprechenden Maschinencode. 
  195.  
  196.  
  197. 1.2.9 Simulation
  198. ----------------
  199.  
  200. Der Computer eignet sich hervorragend dazu, Teile der wirklichen
  201. Welt im Zahlenmodell nachzuspielen oder zu simulieren.  Alles kann
  202. simuliert werden; der Erfolg der Simulation hängt wesentlich davon ab,
  203. wie gut der Programmierer das zu simulierende Problem verstanden hat. 
  204. Da die Ereignisse in der Realität oft von Tausenden von Variablen
  205. abhängen, sind viele Dinge nur schwer wirkungsvoll zu simulieren.  Es
  206. gibt aber etliche andere Probleme, die sehr gut simuliert werden können. 
  207. Aus zwei Gründen sind Simulationen wichtig: Einmal kann man die
  208. Parameter eines Problems variieren und ihren Einfluss auf das Ergebnis
  209. beobachten, auch wenn derartige Experimente im wirklichen Leben zu
  210. kostspielig oder zu gefährlich sind.  Zum zweiten kann man in der
  211. Simulation Situationen schaffen, die in der Realität nicht auftreten
  212. können. 
  213.  
  214.  
  215. 1.2.10 Emulator
  216. ---------------
  217.  
  218. Ein Emulator oder eine Emulation ist ein Sonderfall einer
  219. Simulation.  Wenn auf einem beliebigen Computer das Verhalten eines
  220. anderen Computers simuliert wird, so spricht man von einer Emulation. 
  221. Für den Amiga gibt es eine IBM-PC Emulation, die rein softwaremässig
  222. funktioniert.  Erfahrungsgemäss sind Simulationen eines anderen
  223. Computers nicht so leistungfähig wie das Vorbild, doch meistens reicht
  224. es, um einfache Anwendungen ausführen zu können.  Eine hardwaremässige
  225. Emulation eines IBM-PC ist mit dem Sidecar möglich, einem Zusatzgerät,
  226. das an den Amiga 1000 angeschlossen wird und ihn in einen PC umwandelt. 
  227. Das später in dieser Anleitung noch genau erklärte Computersystem MARS
  228. wird auf dem Amiga nur durch Software emuliert. 
  229.  
  230.  
  231.  
  232.  
  233. 1.3 Geschichte
  234. ______________
  235.  
  236.  
  237. Alles begann mit einem Artikel in der Ausgabe der Zeitschrift
  238. "Spektrum der Wissenschaft" vom April 1984.  Der amerikanische Autor von
  239. Computer-Kurzweil, A. K. Dewdney stellte die Idee eines Spieles vor,
  240. in dem sich zwei Programme in einem Computer auf Leben und Tod
  241. bekämpfen.  Der Sinn des Spieles war es, das gegnerische Programm aus
  242. dem Speicher zu löschen.  Die Programme sollten in einer speziellen, nur
  243. für diesen Zweck entwickelten Sprache geschrieben sein.  Diesem Artikel
  244. folgten in unregelmässigen Zeitabständen weitere über dasselbe Thema,
  245. und in diesen Artikeln erweiterte A. K. Dewdney seine Spielidee mit
  246. neuen Befehlen seiner Programmiersprache und neuen Gedanken zum Aufbau
  247. solcher Kampfprogramme.  Mit der Zeit verbreitete sich das Spiel, und
  248. bald wurden erste Turniere ausgetragen.  Schliesslich wurde die
  249. Internationale Gesellschaft für Core Wars gegründet und legte ein
  250. offizielles Regelwerk vor.  Auf der Basis dieser "Core War Standards"
  251. wurde das hier vorgestellte Programm entwickelt. 
  252.  
  253.  
  254.  
  255.  
  256. 1.4 Core Wars
  257. _____________
  258.  
  259.  
  260.  
  261. 1.4.1 Der Name "Core Wars"
  262. --------------------------
  263.  
  264. Der Name "Core Wars" bedeutet soviel wie "Krieg der Kerne".  Diese
  265. Bezeichnung ist von einer veralteten Speicher-Technologie abgeleitet. 
  266. In den fünfziger und sechziger Jahren wurden Computerspeicher aus
  267. Tausenden von kleinen, kreisrunden Ringen aus magnetischem Material
  268. aufgebaut, die an einem Netzwerk aus feinen Drähten aufgereiht waren. 
  269. Jeder Ring (Durchmesser kleiner als 1 mm) konnte in zwei Richtungen
  270. magnetisiert werden, was den beiden Werten 0 und 1 eines Bits entsprach. 
  271. Diese Datenspeicher wurden Kernspeicher genannt, weil die kleinen Ringe
  272. gewissermassen die Speicherkerne des Computers darstellten.  Die
  273. Kernspeicher waren zu ihrer Zeit Wunder der Feinmechanik: Auf einer
  274. Fläche von etwa 50 mal 50 Millimetern konnten schon 4096 Bits oder 512
  275. Bytes ge speichert werden.  Doch das war vor etwa 20 Jahren: Heute
  276. finden auf der gleichen Fläche rund 15'000 mal mehr Informationen
  277. Platz! In der Computertechnologie wird die CPU mit dem
  278. Schreib-Lesespeicher (RAM) deshalb auch oft als Kern bezeichnet. 
  279.  
  280.  
  281. 1.4.2 Die Sprache der Kampfprogramme
  282. ------------------------------------
  283.  
  284. Die beiden Kampfprogramme für den "Krieg der Kerne" sind in einer
  285. speziellen Sprache geschrieben, die zur Klasse der Assembler gehört:
  286. Der Redcode.  Jede Anweisung eines Redcode-Programmes entspricht einem
  287. Befehl des imaginären Computers, in dem der Kampf stattfindet.  Mit
  288. Assemblersprachen wird vergleichsweise wenig gearbeitet, weil die
  289. Programme schwieriger zu verstehen und zu ändern sind,
  290. als entspechende Programme in einer Hochsprache wie Pascal oder Basic. 
  291. Es gibt allerdings einige Aufgaben, für die sich Assemblersprachen
  292. gut eignen.  Wenn ein Programm so wenig Platz wie möglich belegen oder
  293. so schnell wie möglich laufen soll, wird es normalerweise in einer
  294. Assemblersprache geschrieben.
  295.  
  296. In Assemblersprachen lassen sich überdies einige Dinge machen,
  297. die in einer höheren Programmiersprache so gut wie unmöglich sind.  So
  298. kann man beispielsweise ein Assembler-Programm dazu bringen, seine
  299. eigenen Befehle abzuändern, sich selbst zu kopieren und die Ausführung
  300. an einer völlig anderen Stelle im Speicher fortzusetzen. 
  301.  
  302.  
  303. 1.4.3 Das System "Core Wars"
  304. ----------------------------
  305.  
  306. Core Wars besteht aus vier Hauptbestandteilen: Ein Speicherfeld, in dem
  307. der Kampf stattfinden kann, die Assemblersprache Redcode, einen
  308. imaginären Computer namens MARS (eine Abkürzung von Memory Array Redcode
  309. Simulator und einem Satz von wettstreitenden Kampfprogrammen. 
  310.  
  311.  
  312. 1.4.3.1 Das Speicherfeld
  313.  
  314. Der Speicher, in dem sich die zwei Programme bekämpfen, besteht
  315. aus 8000 Adressen.  Jede Adresse kann eine Redcode-Anweisung mit allen
  316. ihren Parametern aufnehmen.  Das ganze Speicherfeld ist in sich
  317. geschlossen, es besteht aus einer Folge von Adressen von 0 bis 7999. 
  318. Als nächste Adresse nach 7999 folgt wieder die Adresse 0.  MARS
  319. reduziert alle Adressen, die grösser als 7999 sind, indem es den Rest
  320. nach der Division durch 8000 nimmt.  Die Zahl 9378 wird also als Adresse
  321. 1378 interpretiert.  Stellen Sie sich das Speicherfeld von MARS wie
  322. einen grossen Ring aus 8000 Segmenten vor.  In jedem Segment findet eine
  323. Anweisung Platz, die dem Kampfprogramm sagt, was es als nächstes tun
  324. soll.
  325.  
  326.  
  327. 1.4.3.2 Redcode
  328.  
  329. Die Assemblersprache Redcode, in der die Kampfprogramme
  330. geschrieben werden, besteht aus insgesamt 10 Befehlen.  Jeder Befehl hat
  331. eine bestimmte Wirkung auf die Inhalte von beliebigen Adressen im
  332. Speicherfeld von Core Wars.  Es gibt Anweisungen, den Inhalt von einer
  333. Adresse auf eine andere zu übertragen, die Inhalte arithmetisch zu
  334. verändern und innerhalb des Programmes vorwärts und rückwärts zu
  335. springen.  Die Redcode-Befehle verlangen oft Argumente, die z. B. auf
  336. bestimmte Speicherzellen hinweisen oder Zahlenwerte für arithmetische
  337. Operationen darstellen. 
  338.  
  339.  
  340. 1.4.3.3 MARS und Assembler
  341.  
  342. MARS ist der Name des Systems, in dem die Kampfprogramme laufen
  343. können.  MARS existiert nicht in Wirklichkeit, sondern wird durch das
  344. Programm "Core Wars" (nicht zu verwechseln mit Redcode) auf dem Amiga
  345. simuliert.  Der Assembler übersetzt jede Anweisung eines
  346. Redcode-Kampfprogrammes in einen Zahlencode, der dann im
  347. Speicherfeld von MARS abgelegt wird.  Jede Adresse im Speicherfeld kann
  348. eine solche Zahl aufnehmen, mit anderen Worten kann jede einzelne der
  349. 8000 Zellen des Speicherfeldes eine vollständige Redcode-Anweisung
  350. aufnehmen.  Der Abschnitt 1.4 enthält die Redcode-Anweisungen mit
  351. ihren Bedeutungen.  Die Buchstaben A und B stehen für die Argumente
  352. (Zahlenwerte), die die betreffende Anweisung benötigt.  Der
  353. Redcode-Programmierer muss bei jeder Anweisung mindestens ein Argument
  354. angeben, meistens sogar deren zwei. 
  355.  
  356.  
  357. 1.4.4 Die Grundregeln des Spiels
  358. --------------------------------
  359.  
  360. Zwei Kampfprogramme werden von MARS in das Speicherfeld auf zufällig
  361. ausgewählte Plätze geladen.  Kein Programm weiss, wo im Speicher das
  362. andere sitzt.  Die einzige Regel beim Auswählen der Plätze ist, dass
  363. zum Zeitpunkt des Kampfbeginns zwischen den Programmen mindestens 1000
  364. freie Speicherzellen vorhanden sein müssen.  Dann werden die Programme
  365. von MARS abwechslungsweise ausgeführt: Ein einzelner Befehl vom ersten
  366. Programm wird abgearbeitet, dann ein einzelner Befehl des zweiten
  367. Programmes, und so weiter.
  368.  
  369. Was ein Kampfprogramm während des ihm zustehenden
  370. Ausführungszyklus tut, bleibt ganz dem Programmierer überlassen.  Es ist
  371. natürlich bestrebt, das andere Programm zu zerstören, indem es dessen
  372. Befehle löscht.  Möglich ist aber auch eine Defensivstrategie: Ein
  373. Programm kann sich darauf verlegen, erlittene Schäden zu reparieren oder
  374. auszuweichen, wenn es angegriffen wird.
  375.  
  376. Die Schlacht endet, wenn MARS auf einen nicht ausführbaren Befehl
  377. stösst.  Das Programm mit der fehlerhaften Anweisung - vermutlich
  378. eine vom Gegner gelöschte Speicherzelle - wird zum Verlierer
  379. erklärt.  Diese letzte Regel ist hier vorerst etwas vereinfacht
  380. dargestellt worden, weil sich durch einen bestimmten Redcode-Befehl die
  381. Programmausführung auf mehrere, voneinander unabhängige
  382. Einzelprogramme verteilen lässt.  Doch mehr dazu im nächsten
  383. Abschnitt, in dem die verschiedenen Redcode-Befehle erklärt werden. 
  384.  
  385.  
  386.  
  387.  
  388. 1.5 Die Redcode-Befehle
  389. _______________________
  390.  
  391.  
  392.  
  393. 1.5.1 Die Befehlstabelle
  394. ------------------------
  395.  
  396. Anweisung   Argumente   Kurzbeschreibung
  397.  
  398. MOV         A, B        Uebertragen: Uebertrage den Inhalt von 
  399.                         Adresse A auf Adresse B.  
  400.  
  401. ADD         A, B        Addieren: Addiere den Inhalt von Adresse A 
  402.                         zu Adresse B und speichere das Resultat in 
  403.                         Adresse B.  
  404.  
  405. SUB         A, B        Subtrahieren: Ziehe den Inhalt von Adresse A
  406.                         von Adresse B ab und speichere das Resultat 
  407.                         wieder in Adresse B. 
  408.  
  409. JMP         A           Springen: Setze die Ausführung des Programmes
  410.                         um A Zellen weiter vorne oder weiter hinten
  411.                         im Speicher fort. 
  412.  
  413. JMZ         A, B        Springen, wenn Null: Setze die Ausführung des 
  414.                         Programmes um A Zellen weiter vorne oder
  415.                         weiter hinten im Speicher fort, wenn der 
  416.                         Inhalt von Adresse B gleich Null ist. 
  417.  
  418. JMN         A, B        Springen, wenn nicht Null: Setze die Ausführung
  419.                         des Programmes um A Zellen weiter vorne oder
  420.                         weiter hinten im Speicher fort, wenn der Inhalt
  421.                         von Adresse B ungleich Null ist.  
  422.  
  423. DJN         A, B        Vermindern und Springen, wenn nicht Null: Ziehe
  424.                         vom Inhalt von Adresse B eins ab und setze die
  425.                         Ausführung des Programmes um A Zellen weiter
  426.                         vorne oder weiter hinten im Speicher fort, wenn
  427.                         das Resultat ungleich Null ist.  
  428.  
  429. CMP         A, B        Vergleiche: Vergleiche den Inhalt von Adresse 
  430.                         A mit dem von Adresse B und überspringe die 
  431.                         nächste Anweisung, wenn sie ungleich sind; sonst
  432.                         führe die nächste Anweisung aus. 
  433.  
  434. SPL         A           Spalte auf: Spalte die Ausführung des Programmes
  435.                         auf in die nächstfolgende Anweisung und in die
  436.                         Anweisung, die A Zellen weiter vorne oder weiter
  437.                         hinten im Speicher liegt. 
  438.  
  439. DAT         B           Daten: Nicht ausführbare Anweisung: Enthält
  440.                         jedoch Zahlenwerte, auf die zugegriffen werden 
  441.                         kann. 
  442.  
  443.  
  444.  
  445. 1.5.2 Die Argumente
  446. -------------------
  447.  
  448. Wie schon erwähnt, verlangt jeder Redcode-Befehl mindestens ein
  449. Argument.  Diese Argumente sind Zahlenwerte, die die Befehle näher
  450. beschreiben.  Ein Beispiel: In der Anweisung 'JMP -7' ist nur ein
  451. Argument angegeben, weil dieser Befehl zur Ausführung auch nur einen
  452. Wert benötigt.  Die Anweisung bedeutet für MARS, innerhalb des
  453. Programmes um sieben Adressen zurückzuspringen, da das Argument negativ
  454. ist.  Stände die Anweisung 'JMP -7' zufällig an der Adresse 3715 im
  455. Speicherfeld, so würde die Ausführung des Programmes mit dem Befehl in
  456. der Speicherzelle 3715 - 7 = 3708 fortgesetzt. 
  457.  
  458. Diese Methode, eine Position im Speicherfeld zu berechnen, wird
  459. relative Adressierung genannt.  Als Adressierung wird der Weg
  460. bezeichnet, durch den ein System den Wert einer Speicherzelle
  461. herausfindet, die es bearbeiten soll.  In der Sprache Redcode wird nur
  462. die erwähnte relative Art der Adressierung verwendet, deshalb hat ein
  463. Kampfprogramm keine Möglichkeit, seine eigene Position im Speicher zu
  464. erfahren.  Ein Kampfprogramm kann zwar wild in der Gegend herumspringen,
  465. aber es weiss nie, an welcher Stelle im Speicher es sich im Augenblick
  466. befindet.  Da der Speicher wie ein Ring ohne Anfang und Ende aufgebaut
  467. ist, wäre die Angabe einer Position gar nicht sinnvoll, weil die
  468. Adressnummern nur eine Reihenfolge, aber keinen Beginn und kein Ende
  469. festlegen.  Ein weiterer Grund für die ausschliessliche Verwendung der
  470. relativen Adressierung ist die Ausführbarkeit der Kampfprogramme an
  471. beliebigen Positionen im Speicherfeld von MARS, die Programme müssen
  472. relokatibel  sein. 
  473.  
  474. Relokatibel bedeutet: Wenn ein Programm an verschiedenen Stellen im
  475. Speicher eines Computers ausführbar sein soll, so darf es keine
  476. absoluten, also mit festen Zahlenwerten angegebenen, Sprungadressen
  477. besitzen.  Die relative Adressierung, die in Redcode-Programmen
  478. verwendet wird, berücksichtigt diesen Umstand.
  479.  
  480.  
  481. 1.5.3 Die Programmzeiger
  482. ------------------------
  483.  
  484. Um die Sprache der Kampfprogramme, Redcode, zu lernen, ist es
  485. wichtig, einen Begriff aus der Welt der Programme genau zu kennen: Der
  486. Programmzeiger. 
  487.  
  488. Eingangs des ersten Kapitels wurde beschrieben, was ein Programm für
  489. einen Computer überhaupt ist.  Wir sagten, dass ein Programm aus einer
  490. Folge von Anweisungen für den Computer besteht.  Dies ist auch in der
  491. Sprache Redcode der Fall: Ein Kampfprogramm besteht aus einer beliebigen
  492. Anzahl von Redcode-Befehlen oder Programmzeilen, die dem System (hier
  493. also MARS) sagen, was gerade zu tun ist: Eine Zahlenbombe werfen, sich
  494. in Sicherheit bringen, und so weiter.  Damit nun MARS genau weiss,
  495. welche Anweisung innerhalb des Programmes als Nächstes ausgeführt
  496. werden muss, merkt sich MARS für jedes Kampfprogramm die Adresse der
  497. als letztes bearbeiteten Programmzeile.  Um dies etwas plastischer
  498. darzustellen sehen Sie sich bitte das folgende Listing eines
  499. Kampfprogrammes an.  Was die einzelnen Redcode-Befehle bedeuten, ist im
  500. Moment noch unwichtig, Sie sollten sich aber den Aufbau der
  501. Programmzeilen einprägen. 
  502.  
  503.      (2340)    MOV #0, -1 
  504.      (2341)    JMP $-1 
  505.      (2342)    SPL $-2 
  506.      (2343)    MOV $10, $113 
  507.      (2344)    SPL $112 
  508.  
  509. Die Zahlen vor den Redcode-Anweisungen stellen die Adressen der
  510. Speicherzellen dar, in denen die Zeilen gespeichert sind.  Diese
  511. Adressen sind für ein Programm völlig ohne Bedeutung und sind
  512. normalerweise auch nicht bekannt.  Ein Redcode-Programm wird rein
  513. zufällig in das Speicherfeld gesetzt, dieses Programm könnte
  514. irgendwo anders im Speicher stehen.  Hier dienen die Adressen
  515. ausschliesslich dazu, die Bedeutung und Funktion von Programmzeigern zu
  516. erklären. 
  517.  
  518. Zu Beginn der Ausführung des Programmes besitzt der
  519. Programmzeiger den Wert 2340, der Programmzeiger "zeigt" also
  520. gewissermassen auf die erste Anweisung des Kampfprogrammes.  Diese
  521. Anweisung wird ausgeführt und der Programmzeiger um eins aufgezählt, so
  522. dass er nun den Wert 2341 besitzt.  Weil immer mindestens zwei
  523. Kampfprogramme gegeneinander spielen, wird nun auf die gleiche Weise
  524. eine Zeile des gegnerischen Programmes bearbeitet.  Jedes Programm
  525. besitzt natürlich seinen eigenen Programmzeiger, der immer auf die als
  526. nächstes auszuführende Anweisung zeigt. 
  527.  
  528. Jetzt ist wieder unser Kampfprogramm an der Reihe: MARS schaut
  529. sich den Inhalt des Programmzeigers an, der zu unseren Kampfprogramm
  530. gehört.  MARS findet dort die Zahl 2341, die auf die zweite Zeile des
  531. Programmes zeigt.  Wie schon gehabt, wird nun die Anweisung dieser
  532. Zeile ausgeführt und der Programmzeiger wieder um eins erhöht, so dass
  533. er auf die dritte Zeile unseres Kampfprogrammes weist.  Wieder kommt das
  534. gegnerische Programm zum Zuge, und so geht der Kampf weiter, bis alle
  535. Programme eines Spielers zerstört sind und nur noch Redcode-Programme
  536. des Gegners übriggeblieben sind. 
  537.  
  538. Das alles tönt auf den ersten Blick vielleicht etwas
  539. kompliziert, aber durch die Programmzeiger ist zu jedem Zeitpunkt klar
  540. definiert, welche Anweisung von welchem Programm als nächste auszuführen
  541. ist.  Um die Arbeitsweise der Redcode-Anweisungen zu verstehen, ist es
  542. wichtig, dass Ihnen der Sinn und Zweck der Programmzeiger geläufig ist -
  543. der Programmzeiger ist in einem gewissen Sinne das Herz eines
  544. Kampfprogrammes. 
  545.  
  546.  
  547. 1.5.4 Genaue Beschreibung der Redcode-Anweisungen
  548. -------------------------------------------------
  549.  
  550. Die nächsten Abschnitte enthalten zu jedem der zehn Befehle eine
  551. genaue Beschreibung seiner Wirkung auf den Programmzeiger und auf die
  552. Speicherzellen.  Wir haben versucht, möglichst viele Befehle durch
  553. Beispiele zu erklären.  Wir empfehlen Ihnen auch, diese Beispiele
  554. laufend durch das Core Wars Programm auszuprobieren und sie
  555. gegeneinander kämpfen zu lassen.  Wenn Sie eine Idee für ein eigenes
  556. Testprogramm haben, sollten Sie dieses ebenfalls sofort ausprobieren. 
  557. Um mit dem Programm Core Wars zurechtzukommen, können Sie in Kapitel 2
  558. unter "Eine erste Anwendung" nachschlagen.  Dort wird anhand eines Beispiels
  559. gezeigt, wie Sie ein Kampfprogramm assemblieren und eine Schlacht
  560. zwischen zwei Redcode-Programmen starten und am Bildschirm betrachten
  561. können.  Denn auch für MARS und die Sprache Redcode gilt die alte
  562. Wahrheit, dass man Programmieren nur durch Programmieren lernt!
  563.  
  564.  
  565. 1.5.5 DAT - Daten
  566. -----------------
  567.  
  568. Die wichtigste Eigenschaft dieser Anweisung ist, das sie
  569. eigentlich gar keine richtige Anweisung darstellt.  Wenn nämlich der
  570. Programmzeiger eines Kampfprogrammes auf eine Zeile mit einem DAT-Befehl
  571. stösst, wird der Programmzeiger sofort gelöscht und das betreffende
  572. Programm "stirbt".  DAT-Befehle können jedoch auch Bestandteile eines
  573. Programmes sein, sie können Informationen enthalten, die das Programm
  574. während seiner Ausführung benötigt. 
  575.  
  576. Hier ein Beispiel eines DAT-Befehls: "DAT 0".  Die
  577. Speicherzelle, in der dieser Befehl gespeichert ist, darf unter keinen
  578. Umständen ausgeführt werden.  Wenn dies trotzdem der Fall ist, und
  579. ein Programmzeiger eines Kampfprogrammes in diese Anweisung rennt, wird
  580. der Programmzeiger gelöscht.  Die oben angeführte DAT-Zeile kann
  581. aber auch als Munition dienen: Mit dem MOV-Befehl, der gleich erklärt
  582. wird, kann diese Zeile "DAT 0" einer Granate gleich in beliebige
  583. Speicherzellen im ganzen Speicherfeld geworfen werden.  Wenn durch eine
  584. solche DAT-Granate ein gegnerisches Programm getroffen wird, und der
  585. gegnerische Programmzeiger arglos die mit dem DAT-Treffer zerstörte
  586. Programmzeile ausführen will, ist es um ihn geschehen. 
  587.  
  588. Wir werden im Laufe der Erklärungen der anderen Redcode-
  589. Anweisungen weitere Anwendungsmöglichkeiten des DAT-Befehls anhand von
  590. Beispielen aufzeigen.
  591.  
  592.  
  593. 1.5.6 MOV - Uebertragen
  594. -----------------------
  595.  
  596. Diese Anweisung dient dazu, eine bestimmte Zahl oder den Inhalt einer
  597. der Speicherzellen in eine andere Speicherzelle zu übertragen.  Die
  598. Anweisung "MOV 3, 100" (von Englisch move, bewegen) sagt MARS, drei
  599. Schritte oder Adressen im Speicherfeld vorwärts zu gehen und was es dort
  600. findet, in die Zelle 100 Adressen nach dem MOV-Befehl zu kopieren.  Der
  601. alte Inhalt dieser Zelle wird durch den neuen Wert überschrieben.  Die
  602. Argumente der Anweisung "MOV 3, 100" sind direkt, das heisst, sie werden
  603. als Adressen interpretiert, in denen direkt etwas verändert wird.  Um
  604. ein Argument als direkt anzugeben, gibt es zwei Möglichkeiten: zum einen
  605. kann einfach eine Zahl geschrieben werden, zum andern kann der Zahl ein
  606. $-Zeichen vorangestellt werden.  Wenn MARS also eine nackte Zahl als
  607. Argument vorfindet, wird sie als direkt angesehen, und das Gleiche gilt
  608. für eine Zahl mit vorangehendem $-Zeichen.  Sie werden es bereits
  609. vermutet haben: Es gibt noch weitere Arten, wie ein Argument
  610. interpretiert werden kann. 
  611.  
  612. Erlaubt sind zwei zusätzliche Adressierungsmodi.  Wenn einem Argument
  613. ein @-Zeichen voran geht (wir nennen dieses Zeichen seit jeher den
  614. "Klammeraffen"), wird es "indirekt" interpretiert.  Bei der
  615. Anweisung "MOV @3, 100" geschieht folgendes: Der Inhalt der
  616. Adresse, die drei Schritte oder Zellen weiter vorne liegt, wird benutzt,
  617. um schliesslich zu einer weiteren Adresse zu kommen, deren Inhalt dann
  618. hundert Schritte weiter nach vorne kopiert wird.  Um dies etwas klarer
  619. darzustellen, haben wir hier ein Beispiel für die indirekte
  620. Adressierung:
  621.  
  622.      (2719)    MOV @3, 100 
  623.      (2720)    JMP -5 
  624.      (2721)    DAT 50 
  625.      (2722)    DAT -1 
  626.      (2723) 
  627.      - 
  628.      - 
  629.      - 
  630.      (2818)    -
  631.      (2819)    MOV 1, 10  
  632.      (2820)    -
  633.  
  634. Verfolgen wir nun Schritt für Schritt, was geschieht, wenn die Zeile
  635. Nummer 2719 ausgeführt wird.  Dort steht der Befehl "MOV", es
  636. sollen also Daten zwischen zwei Speicherzellen übertragen werden.  Das
  637. erste Argument "@3" ist durch den Klammeraffen adressiert und gibt den
  638. Ort an, von dem die Daten zu holen sind: Als erstes drei Zellen nach
  639. vorne gehen, was zu Zeile Nummer 2722 führt.  In dieser Speicherzelle
  640. steht eine DAT-Anweisung mit dem Argument '-1', und dieser Wert wird nun
  641. als direkt interpretiert.  Das bedeutet, dass wir von Zeile 2722 genau
  642. eine Zelle nach hinten gehen müssen, um den wirklichen Wert zu finden,
  643. der durch den MOV-Befehl übertragen werden soll.  Wir stehen deshalb
  644. vor der Zeile $2722-1=2721$, und in dieser Zeile steht die Anweisung
  645. "DAT 50". 
  646.  
  647. Das zweite Argument unserer MOV-Anweisung ist 100 und wird, da keine
  648. spezielle Adressierungsart angegeben wird, als direkt interpretiert. 
  649. Das Ziel der Verschiebung liegt dadurch 100 Zeilen weiter, also
  650. $2719+100=2819$.  Der MOV-Befehl verschiebt schlussendlich den Inhalt
  651. von Zeile 2721 (DAT 50) nach Zeile 2819.  Der ursprüngliche
  652. Inhalt dieser Speicherzelle wird durch "DAT 50" überschrieben. 
  653. Um anschliessend nicht auf die DAT-Anweisung aufzulaufen und zu sterben,
  654. springt der Programmzähler fünf Schritte zu rück, um dort andere
  655. Anweisungen zu bearbeiten. 
  656.  
  657. Bisher haben Sie die Adressierungsmodi "direkt" mit dem $-Zeichen und
  658. "indirekt" mit dem @-Zeichen kennengelernt.  Die angekündigte dritte
  659. Möglichkeit, ein Argument zu schreiben, ist unmittelbar.  Diese
  660. Adressierungsart wird mit dem #-Zeichen eingeleitet und ist eigentlich
  661. ganz leicht zu verstehen: "MOV #3, 100" überträgt ganz
  662. einfach den Zahlenwert 3 auf die Speicherzelle, die 100 Zeilen weiter
  663. vorne im Speicher steht.  "#" bedeutet, dass die folgende Zahl
  664. unverändert übernommen wird.  Es ist bei der Anwendung der
  665. unmittelbaren Adressierung allerdings Vorsicht geboten, denn nicht alle
  666. Befehle können unmittelbare Werte enthalten.  Der MOV-Befehl darf z. 
  667. B.  als zweites Argument nie eine unmittelbare Zahl enthalten, denn das
  668. würde bedeuten, dass ein absoluter Wert in eine mit ihrer
  669. Zeilennummer angegebenen Speicherzelle übertragen werden kann - und
  670. dies ist nicht gestattet, weil ein Redcode-Kampfprogramm keine
  671. Möglichkeit haben darf, seine eigene Position im Speicher zu erfahren. 
  672. Das gleiche gilt für die Sprungbefehle, doch dazu später noch mehr. 
  673.  
  674. Nach den verschiedenen Adressierungsarten und den ersten beiden
  675. Befehlen, "DAT" und "MOV", ist es an der Zeit, die graue Theorie
  676. in ein erstes Beispielprogramm umzusetzen. 
  677.  
  678.  
  679. 1.5.6.1 Knirps
  680.  
  681.                MOV 0, 1 
  682.  
  683. Knirps ist das einfachste Beispiel eines Redcode-Programmes, das sich
  684. selbst im Speicherfeld fortpflanzen kann.  Es kopiert den Inhalt der
  685. relativen Adresse 0 in die relative Adresse 1, also die nächstfolgende
  686. Adresse.  Es stellt sich nun die Frage, was in der relativen Adresse 0
  687. überhaupt enthalten ist - dort steht nichts anderes als die
  688. Anweisung "MOV 0, 1" selbst! Knirps kopiert sich deshalb bei
  689. jeder Ausführung in die nächstfolgende Speicherzelle.  Der
  690. Programmzeiger wird nach dem Ausführen des Befehls um eins erhöht,
  691. zeigt also ebenfalls auf die nächste Speicherzelle, und der
  692. Kopiervorgang wiederholt sich aufs Neue.  Knirps rollt folglich einer
  693. Dampfwalze gleich mit einer Geschwindigkeit von einer Adresse pro
  694. Ausführunszyklus durch das Feld, eine Spur von "MOV 0, 1" --
  695. Anweisungen hinter sich lassend. 
  696.  
  697. Ein Knirps kann sogar die Seele eines anderen Programmes stehlen:
  698. nämlich dessen Programmzeiger.  Wie es das macht, ist leicht
  699. einzusehen.  Da ein Knirps mit jedem Ausführungszyklus eine
  700. Speicherzelle nach vorne wandert, ist er im Vergleich zu anderen,
  701. grösseren Programmen ziemlich schnell.  Ein Knirps rast von hinten
  702. über ein vor ihm liegendes Programm und überschreibt den Code des
  703. Gegners mit einer unendlichen Folge von "MOV 0, 1" - Befehlen. 
  704. Früher oder später wird das derart unterwanderte Programm
  705. wahrscheinlich in den von Knirps überschriebenen Teil
  706. zurückspringen.  In diesem Moment wird aus ihm ein neuer Knirps.  Es
  707. segelt zwar noch unter der alten Flagge, ist aber fortan dazu verdammt,
  708. dem feindlichen Knirps bis ans Ende der Schlacht willig
  709. hinterherzustapfen. 
  710.  
  711. Spätestens An dieser Stelle sollten Sie einen kleinen Abstecher in
  712. Kapitel zwei machen und sich dort die Einführung zu Core Wars
  713. ansehen.  Sie können dann das eben kennengelernte Kampfprogramm Knirps
  714. gegen eines der auf der Programmdiskette enthaltenen grösseren
  715. Kampfprogramme spielen lassen. 
  716.  
  717.  
  718. 1.5.7 ADD und SUB
  719. -----------------
  720.  
  721. Diese beiden Anweisungen addieren (ADD) oder subtrahieren (SUB) die
  722. Inhalte von zwei Speicherzellen, die durch die beiden Argumente bestimmt
  723. werden.  Das erste Argument kann unmittelbar, direkt oder indirekt
  724. angegeben werden, das zweite darf aber nur indirekt oder direkt sein. 
  725.  
  726. Der Wert des ersten Argumentes wird zum Wert des zweiten
  727. Argumentes addiert und das Ergebnis wird an Stelle des zweiten
  728. Argumentes gespeichert: "ADD #5, 1" holt sich den Inhalt der
  729. Speicherzelle, die einen Schritt weiter vorne liegt und zählt 5 dazu. 
  730. Das Ergebnis wird dann wieder dort gespeichert, wo das zweite Argument
  731. hinzeigt: einen Schritt vor unserer Anweisung. 
  732.  
  733. "SUB" arbeitet genau gleich, ausser dass anstelle einer Addition
  734. eine Subtraktion erfolgt: Das erste Argument wird vom zweiten abgezogen. 
  735.  
  736.  
  737. 1.5.8 Der allgemeine Sprungbefehl JMP
  738. -------------------------------------
  739.  
  740. Wenn der Programmzeiger eines Kampfprogrammes zu einer JMP-Anweisung
  741. gelangt, wird das Argument dieser Anweisung einfach zum Wert des
  742. Programmzeigers hinzugezählt.  Wieder ein Beispiel:
  743.  
  744.      (5632)    MOV #0, 100  
  745.      (5633)    JMP -1 
  746.  
  747. Der Programmzeiger zeigt auf die Anweisung in der Speicherzelle Nr. 
  748. 5632 und der MOV-Befehl wird ausgeführt.  Jetzt wird der Programmzeiger
  749. um eins erhöht und zeigt dadurch auf die nächste Anweisung: "JMP -1". 
  750. Durch den JMP-Befehl wird das Argument dieses Befehls zum Programmzeiger
  751. addiert, also $5633+(-1)=5632$.  "JMP -1" bewirkt hier einen Sprung um
  752. eine Speicherzelle nach hinten, und die Programmzeile mit der
  753. MOV-Anweisung wird erneut ausgeführt.  Diese zwei Zeilen stellen eine
  754. sogenannte "ewige Schleife" dar.  Sie kann nicht mehr verlassen werden
  755. und die zwei Befehle werden ausgeführt, bis der Kampf entschieden ist
  756. oder vom Benützer abgebrochen wird. 
  757.  
  758. Die Adressierung des JMP-Befehls ist wieder etwas eingeschränkt:
  759. Es ist nur möglich, die Argumente entweder direkt (wie in unserem
  760. Beispiel) oder indirekt anzugeben.  Die unmittelbare Adressierung ist
  761. hier verboten, weil sonst an eine absolute Adresse im Speicherfeld
  762. gesprungen werden könnte. 
  763.  
  764. Sie kennen nun genug Befehle, um das erste grössere Kampfprogramm in
  765. seiner Funktion und in seinem Aufbau zu verstehen.  Wenn sie die
  766. folgende Beschreibung durchgelesen haben, können Sie ruhig eine kleine
  767. Verschnaufpause einlegen und Gnom nach Ihren Wünschen abändern. 
  768. Natürlich können und sollen Sie Ihre Kreationen immer wieder mit dem
  769. Programm "Core Wars" ausprobieren. 
  770.  
  771.  
  772. 1.5.8.1 Gnom
  773.  
  774.                DAT -1 
  775.      start     ADD #5, -1 
  776.                MOV #0, @-2 
  777.                JMP -2 
  778.  
  779. Gnom ist ein sehr dummes, aber auch sehr gefährliches Programm. 
  780. Es bombardiert über den ganzen Speicher hinweg jede fünfte Adresse mit
  781. einer Null.  Null ist die Zahl, die eine nichtausführbare DAT-Anweisung
  782. anzeigt, und so kann eine ins feindliche Programm geschossene Null
  783. dieses lahmlegen. 
  784.  
  785. Angenommen, Gnom belegt die absoluten Adressen 1 bis 4.  Unter Adresse 1
  786. steht anfangs "DAT -1", aber die Ausführung des Programmes beginnt mit
  787. dem nächsten Befehl: "ADD #5, -1".  Das Wort "start" anfangs der Zeile
  788. ist ein sogenanntes Schlüsselwort (Symbol).  Es darf in einem Programm
  789. nur einmal benützt werden und bestimmt den Startpunkt des Programmes,
  790. also die Zeile, die als erstes ausgeführt wird.  Dieser erste Befehl
  791. "ADD #5, -1" bewirkt, dass eine 5 zum Inhalt der vorhergehenden Adresse,
  792. nämlich der Anweisung "DAT -1", addiert wird.  Das Ergebnis ist ein "DAT
  793. 4" auf der Absolutadresse 1.  Als nächstes führt Gnom den Befehl auf der
  794. Absolutadresse 3 aus: "MOV #0, @-2".  Darin ist die 0 als unmittelbar
  795. spezifiziert.  Sie wird folglich selbst auf eine Zieladresse übertrag
  796. en, die ihrerseits indirekt angegeben ist und sich folgendermassen
  797. errechnet: Zuerst zählt MARS von Adresse 3 zwei Adressen zurück und
  798. landet so bei Adresse 1.  Sodann nimmt es den dort stehenden Datenwert,
  799. nämlich 4, und interpretiert ihn als Adresse relativ zur gegenwärtigen
  800. Position.  Das heisst, es zählt von Adresse 1 aus 4 Adressen weiter und
  801. legt folglich eine 0 unter Adresse 5 ab. 
  802.  
  803. Die letzte Anweisung von Gnom, "JMP -2", erzeugt eine
  804. Endlosschleife.  Sie verlagert die Ausführung zurück zur
  805. Absolutadresse 2.  Erneut wird also der DAT-Befehl um 5 erhöht, so
  806. dass er den neuen Wert "DAT 9" annimmt.  Im nächsten
  807. Ausführungszyklus wird dem zufolge eine 0 bei der Absolutadresse 10
  808. eingespeichert.  Die folgenden 0-Bomben fallen dann auf die Adressen 15,
  809. 20, 25 und so weiter. 
  810.  
  811. Das Programm selbst ist unbeweglich, aber seine Artillerie bedroht das
  812. ganze Speicherfeld.  Nach etwa 1600 Zyklen schliesslich erreicht Gnom
  813. die Adressen 7990, 7995 und 8000.  Für MARS ist 8000 gleichbedeutend
  814. mit 0, und so hat Gnom haarscharf am Selbstmord vorbeigesteuert und sein
  815. nächstes Geschoss landet wieder auf Adresse 5. 
  816.  
  817.   "Es ist eine bittere Erkenntnis, dass kein stationäres Programm mit
  818.    mehr als vier aufeinanderfolgnden Anweisungen einen Treffer von Gnom
  819.    vermeiden kann."
  820.  
  821.    (Aus: Artikel "Computer Kurzweil, Spektrum der Wissenschaft, 
  822.    Ausgabe vom August 1984, von A. K. Dewdney)
  823.  
  824. Ein gegnerisches Programm hat nur drei Möglichkeiten: Sich
  825. umherzubewegen, um so dem Bombardement auszuweichen, die Treffer
  826. hinzunehmen und den Schaden zu reparieren oder Gnom als erstes zu
  827. erwischen. 
  828.  
  829. Um mit der letzten Strategie durchzukommen, muss ein Programm schon
  830. Glück haben: Es hat ja keine Ahnung, wo im Speicherfeld Gnom sitzt,
  831. und dieser kann im Mittel 1600 Ausführungszyklen durchlaufen, ehe er
  832. einen Treffer hinnehmen muss.  Ist das zweite Programm auch ein Gnom,
  833. gewinnt jedes in etwa 30 Prozent der Fälle, bei 40 Prozent der
  834. Zweikämpfe bekommt dagegen keines der Programme einen tödlichen
  835. Treffer ab. 
  836.  
  837. Rufen Sie sich nun das erste Beispiel, Knirps, wieder in
  838. Erinnerung.  Was geschieht, wenn wir Knirps gegen Gnom antreten lassen?
  839. Probieren Sie den Zweikampf ruhig einige Male mit Core Wars aus und
  840. beobachten Sie im Grafikmodus, wie sich die beiden Programme im
  841. Speicher verhalten.
  842.  
  843. Das Sperrfeuer von Nullen, das Gnom legt, wandert schneller durch das
  844. Speicherfeld als Knirps, aber deswegen ist Gnom nicht unbedingt im
  845. Vorteil.  Selbst wenn er Knirps mit seinem Sperrfeuer einholt, muss er
  846. ihn ja erst treffen.  Die Quote für einen tödlichen Treffer von Knirps
  847. steht etwa 1 zu fünf gegen die DAT-Bomben von Gnom. 
  848.  
  849. Wenn Knirps umgekehrt Gnom zuerst erreicht, marschiert er
  850. höchstwahrscheinlich schnurstracks durch dessen Code hindurch. 
  851. Verlagert Gnoms Anweisung "JMP -2" die Ausführung dann zwei Schritte
  852. zurück, so steht dort die Zeile "MOV 0, 1" von Knirps.  Folglich wird
  853. Gnom "umgedreht" und im ein zweites Knirps-Programm verwandelt, das dem
  854. ersten endlos dem Kreis des MARS-Speichers entlang nachjagt.  Nach den
  855. Regeln von Core Wars wird das Spiel nach einer bestimmten Anzahl von
  856. Ausführungszyklen abgebrochen und endet in diesem Falle unentschieden. 
  857. Es ist noch zu beachten, dass es sich hierbei um das
  858. höchstwahrscheinliche Resultat handelt.  Vielleicht analysieren Sie
  859. selbst die anderen Möglichkeiten und entdecken darunter eine, die ein
  860. ganz verrücktes Ergebnis liefert - mehr wird nicht verraten.
  861.  
  862.  
  863. 1.5.9 Die bedingten Sprünge mit JMZ und JMN
  864. -------------------------------------------
  865.  
  866. Diese beiden Redcode-Befehle verändern wie der JMP-Befehl den
  867. Programmzeiger und erlauben es dadurch, innerhalb eines Programmes
  868. herumzuspringen.  "JMZ" und "JMN" erweitern aber die
  869. Möglichkeiten des einfachen JMP-Befehls: Sie überprüfen zuerst die
  870. Speicherzelle, die durch das zweite Argument bestimmt wird, und
  871. entscheiden dann aufgrund ihres Inhalts, ob gesprungen wird oder nicht. 
  872.  
  873. "JMZ 3, -1" führt den Sprung nur aus, wenn der Inhalt der
  874. Speicherzelle, die eine Adresse weiter hinten im Speicher liegt, genau
  875. Null ist.  Wenn der Inhalt grösser oder kleiner Null ist, wird ganz
  876. normal mit der nächsten Anweisung fortgefahren.  Das erste Argument des
  877. Befehles gibt die Richtung und die Distanz des Sprunges gleich wie beim
  878. JMP-Befehl an.
  879.  
  880. Der andere Befehl, "JMN", ist das Gegenteil von "JMZ": Der
  881. Sprung wird nur dann ausgeführt, wenn der Inhalt der durch das zweite
  882. Argument angegebenen Adresse ungleich Null ist. 
  883.  
  884. Durch diese beiden Befehle können anstelle von Endlosschleifen
  885. auch solche Schleifen programmiert werden, die nur eine von vornherein
  886. bestimmte Anzahl von Durchgängen ausgeführt wird.  Dazu wird eine
  887. Speicherzelle mit einem DAT-Befehl als Zähler verwendet
  888. und bei jedem Schleifendurchlauf durch die SUB- oder die ADD-Anweisung
  889. erhöht oder vermindert.  Der anschliessende JMZ- oder JMN-Befehl
  890. überprüft zuerst die Speicherzelle mit dem Zähler und springt nur an den
  891. Anfang der Schleife zurück, wenn der Zähler die gestellte Bedingung
  892. erfüllt. 
  893.  
  894.  
  895. 1.5.10 Der Vergleichsbefehl CMP
  896. -------------------------------
  897.  
  898. Mit ihm lassen sich zwei beliebige Speicherzellen miteinander
  899. vergleichen und aufgrund des Ergebnisses bestimmte Massnahmen ergreifen. 
  900. Der Inhalt des ersten Argumentes wird mit den Inhalt des zweiten
  901. Argumentes verglichen.  Wenn beide Werte gleich sind, wird die
  902. Anweisung, die sofort nach dem CMP-Befehl folgt, übersprungen und die
  903. Ausführung des Programmes erst bei der übernächsten Zeile
  904. fortgesetzt.  Wenn die beiden Werte ungleich sind, wird die unmittelbar
  905. folgende Anweisung bearbeitet.  Hier ein weiteres Programmbeispiel, das
  906. zwar kein vollständiges Kampfprogramm ist, dafür aber die Anwendung
  907. des Vergleichsbefehls sehr schön aufzeigt:
  908.  
  909.  
  910. 1.5.10.1 Zwillinge
  911.  
  912.                DAT 0 
  913.                DAT 99 
  914.      start     MOV @-2, @-1 
  915.                CMP -3, #9 
  916.                JMP 4 
  917.                ADD #1, -5 
  918.                ADD #1, -5 
  919.                JMP -5 
  920.                MOV #99, 93 
  921.                JMP 93 
  922.  
  923. Unsere ersten beiden Beispiele Knirps und Gnom stehen für eine Klasse
  924. von Programmen, die sich als klein und agressiv, aber nicht als
  925. intelligent klassifizieren lassen.  Auf der nächsten Stufe kommen
  926. Programme, die grösser und etwas weniger angriffslustig, dafür aber klug
  927. genug sind, um mit Programmen der niedrigeren Stufe fertigzuwerden.  Die
  928. klügeren Programme vermögen einem Angriff dadurch zu entgehen, dass sie
  929. sich selbst aus der Gefahrenzone hinauskopieren. 
  930.  
  931. Jedes dieser Programme hat ein Codesegment wie das eines Programmes
  932. namens Zwillinge.  Zwillinge soll kein vollständiges Kampfprogramm sein. 
  933. Seine einzige Aufgabe ist es, 100 Adressen weiter vorn eine Kopie von
  934. sich zu erzeugen und dann die Ausführung an die neue Kopie zu
  935. übertragen. 
  936.  
  937. Zwillinge hat drei Hauptkomponenten.  Zwei DAT-Anweisungen zu Beginn
  938. dienen als Zeiger: Sie geben an, welche Anweisung als nächstes an
  939. welche Stelle im Speicherfeld kopiert werden soll.  Den eigentlichen
  940. Kopiervorgang übernimmt eine Scheife in der Mitte des Programmes; sie
  941. transportiert jeden Befehl zu einer Adresse 100 Schritte hinter seine
  942. aktuellen Position.  Bei jedem Passieren der Schleife werden beide
  943. Zeiger um 1 erhöht, so dass sie eine neue Quell- und Zieladresse
  944. bezeichnen.  Ein Vergleichsbefehl innerhalb der Schleife prüft den
  945. Wert der ersten DAT-Anweisung.  Sobald sie neunmal erhöht wurde, ist
  946. das ganze Programm kopiert, und die Schleife wird verlassen.  Nur eine
  947. letzte Korrektur fehlt noch: Die Zieladresse steht in der zweiten
  948. Anweisung des Programmes und hat einen Anfangswert von "DAT 99";
  949. als sie kopiert wurde, war sie jedoch bereits um 1 erhöht, so dass in
  950. der neuen Version des Programmes "DAT 100" steht.  Dieser
  951. Uebertragungsfehler wird durch den Befehl "MOV #99, 93"
  952. korrigiert und dann die Ausführung des Programmes durch den letzten
  953. JMP-Befehl an die neue Kopie übergeben. 
  954.  
  955.  
  956. 1.5.11 Die Spaltung von Programmen durch SPL
  957. --------------------------------------------
  958.  
  959. Dies ist der letzte noch unbekannte Redcode-Befehl.  "SPL" kommt
  960. vom englischen Verb 'to split', das auf Deutsch 'spalten' bedeutet.  Und
  961. genau das bewirkt dieser Befehl: Wenn der Programmzeiger eines
  962. Redcode-Programmes auf eine SPL-Anweisung trifft, wird das Programm an
  963. zwei Stellen gleichzeitig weitergeführt: Das erste Mal mit der Zeile,
  964. die gleich nach der SPL-Anweisung folgt und das zweite Mal an der
  965. Adresse, die durch das Argument der SPL-Anweisung bestimmt wird. 
  966.  
  967.  
  968.      (0143)    -
  969.      (0144)    MOV #0, 100  
  970.      (0145)    SPL 2 
  971.      (0146)    JMP 101  
  972.      (0147)    -
  973.  
  974. Dieses Programmfragment zeigt den Gebrauch von "SPL": der
  975. Programmzeiger wird irgendwann auf Zeile 145 treffen.  Durch diese Zeile
  976. wird ein neuer Programmzeiger geboren, der seine Tätigkeit in diesem
  977. Fall zwei Zeilen weiter vorne bei Adresse 147 aufnimmt.  Gleichzeitig
  978. läuft aber der ursprüngliche Programmzeiger weiter auf Zeile Nummer 146
  979. und springt von dort 101 Programmzeilen weiter nach vorne auf Zeile 
  980. $146+101=247$.  Dieser Vorgang kann fast beliebig oft wiederholt werden. 
  981. So ist es möglich, dass aus einem Anfangsprogramm maximal 63 neue
  982. Programme entstehen, die alle gleichzeitig abgearbeitet werden.  Diese
  983. Aufspaltung von Programmen wirft aber einige Probleme auf, wie Sie
  984. gleich sehen werden. 
  985.  
  986.  
  987.  
  988.  
  989. 1.6 Der Split-Befehl SPL und seine Wirkung
  990. __________________________________________
  991.  
  992.  
  993.  
  994. 1.6.1 Die Ausführung mehrerer Programme
  995. ---------------------------------------
  996.  
  997. Durch den SPL-Befehl erhalten die Redcode-Programmierer die
  998. Möglichkeit, mehrere Programme gleichzeitig unter derselben Flagge
  999. laufen zu lassen.  Entsprechend muss festgelegt werden, wie MARS in
  1000. diesem Fall die Rechenzeiten verteilt.  Das kann auf zweierlei Arten
  1001. geschehen. 
  1002.  
  1003. Angenommen, dem einen Spieler gehörten die Programme $A_1$, $A_2$ und
  1004. $A_3$, dem anderen $B_1$ und $B_2$.  Eine Möglichkeit wäre, erst
  1005. alle Programme des einen und dann die des anderen Spielers laufen zu
  1006. lassen.  Die Reihenfolge der Ausführung wäre also $A_1$, $A_2$,
  1007. $A_3$ und dann $B_1$ und $B_2$.  Dieser Zyklus würde sich endlos
  1008. wiederholen.  Bei der anderen Möglichkeit wechseln sich die Programme
  1009. der Spieler ab.  Die Reihenfolge wäre dann $A_1$, $B_1$, $A_2$, $B_2$,
  1010. $A_3$, $B_1$ und so weiter. 
  1011.  
  1012. Beide Vorgehensweisen wirken sich ganz unterschiedlich aus.  Die
  1013. erste Methode begünstigt den, der möglichst viele Programme ins Spiel
  1014. bringt, was der Entwicklung intelligenter Strategien wohl kaum
  1015. förderlich ist.  Die Zweite dagegen bedeutet, dass ein Programm um so
  1016. seltener drankommt, je mehr Progrmme ein Spieler laufen hat.  Weil sich
  1017. der Vorteil einer ungehemmten Programmvermehrung auf diese Weise schnell
  1018. aufhebt, gab der Erfinder von MARS diesem Verfahren den Vorzug. Ziel
  1019. des Spieles ist es jetzt, alle feindlichen Programme zum Anhalten zu
  1020. bringen. 
  1021.  
  1022. Der Redcode-Programmierer muss sich beim Schreiben eines
  1023. Programmes, das sich mehrmals aufteilt, vor Augen halten, dass er zwar
  1024. mehrere Programmzeiger gleichzeitig laufen lassen kann, aber dass
  1025. dadurch natürlich ein einzelnes seiner Programme viel langsa mer läuft. 
  1026.  
  1027. Als nächstes wollen wir noch einige Programme behandeln, die die
  1028. Anwendung des SPL-Befehls anschaulicher darstellen:
  1029.  
  1030.  
  1031. 1.6.2 Die Knirps-Kanone
  1032. -----------------------
  1033.  
  1034.      start     SPL 2 
  1035.                JMP -1 
  1036.                MOV 0, 1 
  1037.  
  1038. Was passiert, wenn die erste Zeile dieses Programmes an die Reihe kommt?
  1039. Die Anweisung "SPL 2" bedeutet, dass sich das Programm aufteilt und zwei
  1040. Programmzeilen ausgeführt werden: "JMP -1" und "MOV 0, 1".  Die erste
  1041. Instruktion bewirkt einen Rücksprung zur SPL-Anweisung, während die
  1042. zweite einen Knirps (erinnern Sie sich? Das erste Programmbeispiel...)
  1043. in Marsch setzt.  Dieser wälzt sich stur durch den Speicher, denn die
  1044. Zieladresse der MOV-Anweisung ist stets die jeweils nächste Adresse. 
  1045. Mit jedem zweiten Programmzyklus wird also ein neuer Knirps erzeugt, und
  1046. so schiebt sich eine Marschkolonne von 63 Knirpsen durch die Kern-Arena
  1047. - bereit, jedes feindliche Programm einfach niederzuwalzen. 
  1048.  
  1049. Auf den ersten Blick scheint gegen ein solches Heer von Knirpsen
  1050. keine Verteidigung möglich, aber der Schein trügt:
  1051.  
  1052.  
  1053. 1.6.3 Das Knirps-Grab
  1054. ---------------------
  1055.     
  1056.                MOV #0, -1 
  1057.                JMP -1 
  1058.  
  1059. Dies ist wiederum nur ein Programmfragment, das zu einem
  1060. beliebigen grösseren Kampfprogramm gehören kann, das seine untere Flanke
  1061. vor Knirpsen schützen will.  Diese zwei Zeilen namens Knirps-Grab
  1062. (manchmal auch Knirpsfalle genannt) werden durch eine SPL-Anweisung
  1063. innerhalb des grossen Programmes einmal gestartet und arbeiten danach
  1064. ohne weitere Unterstützung des grossen Programmes weiter. 
  1065.  
  1066. Bei jeder Ausführung plaziert Knirps-Grab eine Null direkt vor sich -
  1067. in der Hoffnung, einen herannahenden Knirps damit zu treffen.  Hier ist
  1068. die Anfangs vereinbarte Ausführungsregel entscheidend.  Wenn
  1069. Kirps-Kanone dem Spieler A gehört und Knirps-Grab dem Spieler B, dann
  1070. braucht A $n$ Züge, um $n$ Knirpse eine Zelle weiter nach vorn zu
  1071. bewegen; nur einer dieser Knirpse kann auf dem Speicherplatz vor
  1072. Knirps-Grab landen.  Unter sonst gleichen Bedingungen braucht B sein
  1073. Knirps-Grab dagegen nur einmal auszuführen, um einen ankommenden
  1074. Knirps zu löschen.  Versuchen Sie, eigene Programme zu schreiben, die
  1075. das Knirps-Grab verwenden, um sich vor von hinten anrollenden Knirpsen
  1076. zu schützen. 
  1077.  
  1078.  
  1079.  
  1080.  
  1081. 1.7 Die Regeln auf einen Blick
  1082. ______________________________
  1083.  
  1084.  
  1085.  
  1086. Das MARS-System besteht aus dem MARS Simulationsprogramm und dem
  1087. Redcode-Assembler.  Wenn Sie nicht mit dem Texteditor des Programmes
  1088. "Core Wars" arbeiten wollen, benötigen Sie darüberhinaus einen
  1089. beliebigen Editor oder eine Textverarbeitung, um die Kampfprogramme zu
  1090. schreiben.  Wenn eine Textverarbeitung verwendet wird, ist es wichtig,
  1091. dass sie in der Lage ist, Texte im ASCII-Format abzuspeichern. 
  1092.  
  1093. Der Redcode-Assembler übersetzt die Programme, die im
  1094. ASCII-Format vorliegen müssen, in den für das MARS Simulationsprogramm
  1095. ausführbaren Programmcode, der auch Objektcode genannt wird.  Man sagt
  1096. auch: Der Redcode-Assembler übersetzt den Quelltext in den Objektcode.
  1097.  
  1098. Der MARS-Emulator lädt zwei der Kampfprogramme in das Spielfeld, ein
  1099. 8000 Zellen umfassender Speicher, der von MARS simuliert und verwaltet
  1100. wird.  Die Positionen, an denen die beiden Kampfprogramme A und B im
  1101. Speicherfeld abgelegt werden, werden zufällig ausgewählt, sie
  1102. müssen jedoch mindestens 1000 Zellen voneinander entfernt sein. 
  1103.  
  1104. Nun folgt die Ausführung der beiden Redcode-Programme.  Es wird
  1105. abwechslungsweise eine Anweisung von Partei A und anschliessend eine
  1106. Anweisung von Partei B ausgeführt.  Dieser Zyklus wiederholt sich so
  1107. lange, bis alle Programme einer Partei zerstört sind oder bis eine
  1108. bestimmte Anzahl von Zyklen ausgeführt wurden.  Ein Kampfprogramm gilt
  1109. als zerstört, wenn es versucht, eine DAT-Anweisung auszuführen.
  1110. Dabei ist es egal, ob die DAT-Anweisung von Anfang an an dieser Stelle
  1111. stand oder vom Gegner dorthin kopiert wurde.
  1112.  
  1113. Der Gewinner des Spiels ist das Programm, das noch läuft (intakt ist),
  1114. wenn alle anderen Programme schon zerstört sind.  Es gibt zwei
  1115. Fälle, in denen ein Kampf unentschieden ausgehen kann: Entweder wird
  1116. eine bestimmte (wählbare) Anzahl von Ausführungszyklen
  1117. überschritten, oder beide Programme haben zum Zeitpunkt der
  1118. Zerstörung genau dieselbe Anzahl gültiger Instruktionen ausgeführt
  1119.  
  1120. Das Speicherfeld, in dem der Kampf der Programme stattfindet, ist ein in
  1121. sich geschlossener Bereich.  Nach der Speicherzelle mit der Adresse 7999
  1122. folgt wieder die Adresse 0 und umgekehrt.  Die Adressierung der
  1123. Redcode-Befehle ist immer relativ zu der augenblicklichen Position des
  1124. Programmes im Speicherfeld oder mit anderen Worten relativ zum Inhalt
  1125. des Programmzeigers.  Ein Redcode-Programm kann zu jeder Zeit den Inhalt
  1126. einer beliebigen Speicherzelle (relativ adressiert) im Speicherfeld
  1127. erfahren oder einen Sprung zu dieser Speicherzelle ausführen. 
  1128.  
  1129. Der SPL-Befehl ermöglicht es, dass mehrere Programme für
  1130. den gleichen Spieler laufen können.  Die Anzahl der gleichzeitig
  1131. laufenden Programme ist auf 64 pro Spieler beschränkt.  Das ergibt,
  1132. sofern beide Spieler dieses Maximum ausnützen, im besten Falle 128
  1133. gleichzeitig laufende Programme. 
  1134.  
  1135.  
  1136.  
  1137.  
  1138. 1.8 Erleichterungen
  1139. ___________________
  1140.  
  1141.  
  1142.  
  1143. Der Redcode-Assembler bietet einige Erleichterungen beim Schreiben eines
  1144. Kampfprogrammes.  Es handelt sich um einen "symbolischen Assembler",
  1145. der in der Lage ist, sich bestimmte Adressen unter einem Namen oder eben
  1146. dem Symbol zu merken.  Dies bringt den Vorteil, dass die Sprungdistanzen
  1147. bei den Befehlen SPL, JMP, JMN und JMZ nicht mehr von Hand ausgezählt
  1148. werden müssen.  Man gibt einfach anstelle der Sprungdistanz in Zahlen
  1149. einen Namen ein.  Dieser Name wird dann nochmals an den Beginn der
  1150. Zeile, zu der gesprungen werden soll, gesetzt.  Ein Beispiel ist das
  1151. Kampfprogramm Gnom, das schon in einem früheren Abschnitt erklärt
  1152. wurde.  Hier ist das Programm, so wie es ohne Symbole geschrieben wird:
  1153.  
  1154.                DAT -1 
  1155.      start     ADD #5, -1 
  1156.                MOV #0, @-2 
  1157.                JMP -2 
  1158.  
  1159. Streng genommen ist das wort "start" auch ein Symbol, aber
  1160. dieser Name ist reserviert und zeigt dem Assembler, an welcher Zeile das
  1161. Programm später gestartet werden muss. "start" steht immer vor der
  1162. als erstes auszuführenden Programmzeile und darf deshalb nur einmal am
  1163. Beginn einer Zeile verwendet werden. Ein Programm ohne das
  1164. "start"-Symbol wird bei der ersten Zeile im Quelltext gestartet.
  1165.  
  1166.  
  1167. Und so sieht das Programm aus, wenn mit Symbolen gearbeitet werden kann:
  1168.  
  1169.      adresse   DAT -1 
  1170.      start     ADD #5, adresse 
  1171.                MOV #0, @adresse 
  1172.                JMP start 
  1173.  
  1174. Der JMP-Befehl in der letzten Zeile springt immer noch um zwei Adressen
  1175. zurück, aber anstelle der Zahl -2 steht dort nun das Symbol "start". 
  1176. Der Assembler berechnet beim Assemblieren des Programmes die Distanz
  1177. zwischen dem JMP-Befehl und der Zeile, an deren Anfang das Symbol
  1178. "start" geschrieben steht, und fügt dann anstelle von "JMP start" die
  1179. Zeile "JMP -2" in das Programm ein.  Genau gleich funktioniert das Ganze
  1180. bei den beiden vorhergehenden Programmzeilen "ADD #5, adresse" und "MOV
  1181. #0, @adresse".  Die Befehle beziehen sich immer noch auf die
  1182. ursprünglichen Zeilen, aber die Distanzen werden aufgrund der Symbole
  1183. vom Assembler ausgerechnet.  Wir empfehlen die Verwendung von Symbolen,
  1184. denn ein Programm wie Gnom wird durch die verwendeten Namen
  1185. verständlicher und leichter lesbar. 
  1186.  
  1187. Mit Symbolen kann auch gerechnet werden.  Man muss dazu wissen, dass
  1188. jedes Symbol mit der Zahl in Verbindung gebracht wird, die sich aus der
  1189. Numerierung der Programmzeilen bei Null beginnend ergibt.  In unserem
  1190. Beispiel würde das Symbol "adresse" die Zahl 0 und das Symbol "start"
  1191. die Zahl 1 enthalten.  Anstelle von "MOV #0, @adresse" könnte auch
  1192. geschrieben werden: "MOV #start + adresse - 10, @adresse".  Dies
  1193. Formulierung ergäbe zwar keinen Sinn, aber es zeigt, dass mit Symbolen
  1194. und den Operatoren "+" und "-" bestimmte Werte ausgerechnet werden
  1195. können, die dann vom Assembler als Zahlen eingesetzt werden.  Der Term
  1196. "start + adresse - 10" ergäbe in diesem Fall 1 + 0 - 10 = -9. 
  1197.  
  1198. Bei der Benützung von Symbolen ist eigentlich nur wichtig, dass jedes
  1199. Symbol an irgendeiner Stelle im Programm definiert wird.  Ein Symbol
  1200. gilt als definiert, wenn es in einer Zeile vor dem Redcode-Befehl
  1201. beginnend mit der ersten Zeichen der Zeile auftaucht.  Ein Symbol darf
  1202. beliebig oft als Argument eines Redcode-Befehls verwendet werden, aber
  1203. es darf nur genau einmal pro Programmtext definiert werden. 
  1204.  
  1205. Es existiert neben "start" noch ein weiteres reserviertes Symbol, das
  1206. *-Zeichen.  Es bezieht sich immer auf die aktuelle Programmzeile, in der
  1207. es sich befindet.  Wieder zeigt ein Beispiel die Funktion des *-Symbols:
  1208.  
  1209. Diese Version des Programmes Gnom
  1210.  
  1211.                DAT -1 
  1212.      start     ADD #5, -1 
  1213.                MOV #0, @-2 
  1214.                JMP -2 
  1215.  
  1216. bewirkt genau dasselbe wie diese Version:
  1217.  
  1218.                DAT -1 
  1219.      start     ADD #5, -1 adresse  
  1220.                MOV adresse, @-2 
  1221.                JMP -2 
  1222.  
  1223. Doch das Ganze kann auch so formuliert werden:
  1224.  
  1225.                DAT -1  
  1226.      start     ADD #5, -1 
  1227.                MOV *, @-2 
  1228.                JMP -2 
  1229.  
  1230. Das *-Zeichen (Vorsicht: es hat bei Redcode nichts mit einer
  1231. Multiplikation zu tun, wie man von anderen Sprachen her vermuten
  1232. könnte) wird beim Assemblieren durch den Wert ersetzt, den ein
  1233. normales Symbol auch hätte, wenn es in dieser Zeile definiert würde
  1234. - nämlich exakt Null.  Deshalb können Sie sich eine ausschliesslich
  1235. für eine Zeile benützte Definition ersparen, wenn sie den
  1236. reservierten Symbolnamen '*' benutzen. 
  1237.  
  1238. Weitere Informationen, wie Sie einen Programmtext genau
  1239. schreiben müssen und welche Beschränkungen Sie dabei berücksichtigen
  1240. sollten, finden Sie im zweiten Kapitel dieser Anleitung: Der Abschnitt
  1241. 2.4 befasst sich mit dem Assembler des Programmes "Core Wars". 
  1242.  
  1243.  
  1244.  
  1245.  
  1246. 1.9 Eine neue Adressierungsart
  1247. ______________________________
  1248.  
  1249.  
  1250.  
  1251. Wir haben Ihnen noch eine letzte Adressierungsart vorenthalten.  Sie
  1252. kennen die unmittelbare, die direkte und die indirekte Adressierung von
  1253. Argumenten für die Redcode-Befehle.  Wenn Sie den einen oder andern
  1254. dieser drei Modi noch nicht hundertprozentig verstanden haben, sollten
  1255. Sie sich nochmals die Abschnitte 1.3 und 1.4 dieses Kapitels vornehmen. 
  1256. Probieren Sie die dort abgedruckten Beispielprogramme nochmals mit dem
  1257. "Core Wars"--Programm aus.  Eine gute Hilfe zum Verstehen der
  1258. Adressierunsarten ist auch das genaue Verfolgen der disassemblierten
  1259. (zurückübersetzten) Programmzeilen eines schwierigen Programmes. 
  1260. Nähere Informationen finden Sie im Abschnitt 2.8 ("Die
  1261. Statusanzeige") im zweiten Kapitel. 
  1262.  
  1263. Doch nun zurück zu unserer vierten Adressierungsart.  Sie nennt sich
  1264. "indirekt-dekrement", und wie Sie vielleicht vermuten, handelt
  1265. es sich dabei um eine Abwandlung der indirekten Adressierung.  Der Name
  1266. tönt komplizierter, als sich die Sache in der MARS-Wirklichkeit verhält.
  1267.  
  1268. Wir wollen den Vorgang der indirekten Adressierung nochmals
  1269. aufwärmen: Das Argument des aktuellen Redcode-Befehls zeigt direkt auf
  1270. eine beliebige Adresse.  Der Inhalt dieser Adresse wird nun ein zweites
  1271. Mal direkt interpretiert und zeigt dadurch auf die entgültige
  1272. Adresse, die dann je nach Befehl verwendet oder verändert wird. 
  1273.  
  1274. Dekrementieren bedeutet, einen Wert um eine bestimmte Zahl zu
  1275. vermindern.  In der Computertechnologie ist diese Zahl typischerweise
  1276. genau eins, so auch bei der indirekt-dekrement Adressierung.  Wenn MARS
  1277. auf eine Anweisung trifft, deren Argument oder Argumemte auf diese Weise
  1278. adressiert sind, laufen folgende Schritte in der angegebenen Reihenfolge
  1279. ab:
  1280.  
  1281.  
  1282. 1.   Das betreffende Argument des Redcode-Befehls wird direkt
  1283.      interpretiert und führt so auf eine Zwischenadresse.  Bis jetzt
  1284.      geschieht genau dasselbe wie bei der indirekten Adressierung. 
  1285.  
  1286. 2.   Nun wird dekrementiert: Vom Inhalt dieser Zwischenadresse wird eins
  1287.      abgezogen (subtrahiert) und das Ergebnis der Rechnung wird wieder 
  1288.      in die Zwischenadresse zurückgespeichert. 
  1289.  
  1290. 3.   Ab jetzt läuft alles wieder wie bei der indirekten Adressierung: Der
  1291.      neue Inhalt der Zwischenadresse wird als direkt angesehen und zeigt
  1292.      deshalb auf die Endadresse, mit der oder mit deren Inhalt (je nach
  1293.      Befehl) weitergearbeitet wird.  Uff. 
  1294.  
  1295. Wenn Sie die neue Adressierungsart einigermassen verdaut haben, können
  1296. wir Ihnen Abschnitt 3.1 im dritten Kapitel empfehlen.  Dort sind weitere
  1297. Redcode-Programme aufgelistet und werden etwas auseinandergenommen.  Vor
  1298. allem das Gewinnerprogramm der ersten Core Wars Weltmeisterschaft im
  1299. Jahre 1986 bedient sich ausgiebig der indirekt-dekrement Adressierung. 
  1300.  
  1301.  
  1302.  
  1303.  
  1304. 1.10 Auf den zweiten Blick
  1305. __________________________
  1306.  
  1307.  
  1308.  
  1309. An dieser Stelle haben Sie nun das Grundwissen eines
  1310. Redcode-Programmierers und Sie können behaupten, die Regeln der Sprache zu
  1311. beherrschen.  Alles, was ab jetzt noch kommt, sollte keine nennenswerten
  1312. Schwierigkeiten mehr bieten, weil neue Tatsachen nur noch auf der bis
  1313. zu diesem Punkt behandelten Theorie basieren. 
  1314.  
  1315. Doch wie in jeder Programmiersprache gibt es auch in Redcode
  1316. verschiedene Sonderfälle, die viel Zeit und Nerven kosten können, wenn
  1317. man sie nicht in ihrer Wirkung kennt.  Deshalb haben wir eine Liste der
  1318. Eigenheiten von Redcode mit der Erklärung der jeweiligen Falltüren
  1319. erstellt. 
  1320.  
  1321.  
  1322. 1.10.1 Unmittelbare Adressierung bei Sprungbefehlen
  1323. ---------------------------------------------------
  1324.  
  1325. Das Ziel eines Sprunges kann, obwohl vier verschiedene
  1326. Adressierungsarten bekannt sind, nur durch die drei Modi "direkt",
  1327. "indirekt" und "indirekt-inkrement" angegeben werden.  Die
  1328. unmittelbare Adressierung ist jeweils bei der Sprungadresse der Befehle
  1329. "JMP", "JMZ", "JMN", "DJN" und "SPL" nicht erlaubt!
  1330. Das ist darin begründet, dass jede Adressierung eine Speicherzelle nie
  1331. explizit oder anders ausgedrückt nie direkt mit ihrer wirklichen
  1332. Nummer erreichen kann.  Eine andere Speicherzelle wird bei Redcode immer
  1333. relativ zur augenblicklichen Position im Speicher angesprochen.  Dadurch
  1334. wird verhindert dass 
  1335.  
  1336. a)   ein Redcode-Programm seine eigene Position im Speicherfeld erfahren
  1337.      kann und dass
  1338.  
  1339. b)   alle Redcode-Programme lauffähig sind, egal an welche Position des
  1340.      Speichers sie zu Beginn eines Kampfes geladen wurden. 
  1341.  
  1342.  
  1343.  
  1344. 1.10.2 Unmittelbare Adressierung bei MOV, ADD, SUB und DJN
  1345. ----------------------------------------------------------
  1346.  
  1347. Auf den ersten Blick haben diese vier Befehle nicht viel gemeinsam, aber
  1348. dennoch gehören sie zusammen unter diesen Titel: Alle vier verändern den
  1349. Inhalt einer beliebigen Speicherzelle.  "ADD" und "SUB" führen mit der
  1350. durch das zweite Argument bestimmten Speicherzelle eine Subtraktion oder
  1351. Addition durch.  "MOV" kopiert den Inhalt einer Adresse in eine andere
  1352. Adresse, die durch das zweite Argument angegeben wird.  Der alte Inhalt
  1353. dieser Zieladresse geht dabei verloren, sie wird also ebenfalls
  1354. verändert.  Der vierte im Bunde ist der Befehl "DJN", der eine
  1355. Speicherzelle um eins vermindert und dann den neuen Inhalt dieser Zelle
  1356. mit Null vergleicht. 
  1357.  
  1358. Bei den genannten Befehlen ist es ebenfalls nicht erlaubt, bei der
  1359. Angabe der Zieladresse den Modus unmittelbar zu verwenden.  Die Gründe
  1360. dafür sind dieselben wie bei den Sprungbefehlen: Ein Redcode-Programm
  1361. darf seine Position im Speicher nicht erfahren und soll an jeder Stelle
  1362. im Speicherfeld lauffähig sein. 
  1363.  
  1364.  
  1365. 1.10.3 Der Vergleichsbefehl CMP
  1366. -------------------------------
  1367.  
  1368. Bei seiner Anwendung muss beachtet werden, dass entweder ganze
  1369. Speicherzellen oder nur einzelne Werte verglichen werden können.  Wir
  1370. rufen uns in Erinnerung, dass eine MARS-Speicherzelle einen
  1371. vollständigen Redcode-Befehl, also das Befehlswort mit seinen maximal
  1372. zwei Argumenten und Adressierungsmodi, aufnehmen kann.  Ob nun nur zwei
  1373. Werte oder gleich eine ganze Speicherzelle verglichen wird, hängt von
  1374. der verwendeten Adressierungsart ab. 
  1375.  
  1376. Wenn weder das erste noch das zweite Argument des CMP-Befehls
  1377. unmittelbar adressiert ist, weisen die Argumente auf "ganze"
  1378. Speicherzellen.  Somit werden beide Zellen, die durch die Argumente
  1379. bestimmt sind, vollständig verglichen.  Vollständig bedeutet, dass
  1380. sowohl der Befehl, als auch die Argumentwerte und die Adressierungsmodi
  1381. verglichen werden.  Der Vergleich ist nur dann wahr, wenn wirklich alle
  1382. diese Punkte der beiden Befehle übereinstimmen.  Der Verlgeich ist
  1383. aber falsch, sobald auch nur einer der Punkte der einen Adresse von dem
  1384. entsprechenden Punkt der anderen Adresse abweicht. 
  1385.  
  1386. Einzelne Werte dagegen werden verglichen, wenn eines der beiden
  1387. Argumente eine unmittelbare Zahl ist, z.B.  #8.  Normalerweise ist
  1388. nur eines der Argumente unmittelbar, weil ein Vergleich der beiden
  1389. Zahlen #3 und #9 von vornherein bekannt ist und deshalb keinen Sinn
  1390. ergibt.  Das andere Argument ist also direkt, indirekt oder
  1391. indirekt-dekrement adressiert und stellt eine Ziel- oder
  1392. Vergleichsadresse dar.  In dieser Adresse wird der Wert, der das zweite
  1393. (B-) Argument darstellt, mit dem unmittelbaren Wert des CMP-Befehls
  1394. verglichen.  In diesem Fall werden folglich nur zwei Zahlen verglichen:
  1395. Das B-Argument der Zieladresse und die unmittelbare Zahl in der
  1396. CMP-Anweisung. 
  1397.  
  1398.  
  1399. 1.10.4 DAT-Befehle mit dem MOV-Befehl kopieren
  1400. ----------------------------------------------
  1401.  
  1402. Der MOV-Befehl dient in erster Linie dazu, ganze Programmzeilen
  1403. an eine andere Stelle im Speicherfeld zu kopieren oder bestimmte Zahlen
  1404. als DAT-Befehle im Speicher abzulegen. 
  1405.  
  1406. Wenn in einer MOV-Anweisung die Quelladresse (das erste Argument)
  1407. unmittelbar angegeben ist, wird an die Zieladresse (das zweite Argument)
  1408. ein DAT-Befehl kopiert.  Dieser DAT-Befehl besitzt den Wert, der durch
  1409. die Zieladresse unmittelbar angegeben ist.  Die Anweisung "MOV #8, 10"
  1410. kopiert deshalb einen "DAT 8"-Befehl auf die Zieladresse, die 10 Zeilen
  1411. weiter hinten im Speicherfeld liegt. 
  1412.  
  1413. Ist jedoch die Quelladresse direkt, indirekt oder indirekt-inkrement
  1414. adressiert, wird die ganze Programmzeile, die durch die Quelladresse
  1415. bestimmt wird, in die Speicherzelle kopiert, die durch die Zieladresse
  1416. des MOV-Befehls angegeben wird. 
  1417.  
  1418. Wichtig bei der MOV-Anweisung ist, dass Sie wissen, in welchen Fällen
  1419. neue DAT-Befehle geschaffen und wann ganze Programmzeilen kopiert
  1420. werden. 
  1421.  
  1422.  
  1423. 1.10.5 Die Anwendung von ADD und SUB
  1424. ------------------------------------
  1425.  
  1426. Diese Befehle dienen zum Addieren und Subtrahieren in Speicherzellen. 
  1427. Diese Operationen können sowohl auf Zahlen (unmittelbar) als auch
  1428. Programmzeilen (direkt, indirekt und indirekt-inkrement) angewandt
  1429. werden.  Beachten Sie aber, dass sich die beiden Befehle je nach
  1430. Anweisung unterschiedlich verhalten können. 
  1431.  
  1432. Jede Zelle im MARS-Speicherfeld besteht aus einer Anweisung und zwei
  1433. Argumenten.  Es spielt dabei keine Rolle, ob der enthaltene Befehl zwei
  1434. oder nur ein Argument benötigt: Im Speicher belegt er eine ganze
  1435. Zeile.  Wenn zwei Zeilen addiert oder subtrahiert werden sollen, erfolgt
  1436. die Operation in zwei Schritten: Zuerst wird Argument A der ersten Zeile
  1437. mit Argument A der zweiten Zeile verrechnet, anschliessend geschieht
  1438. dasselbe mit den B-Argumenten.  Das heisst, dass die Addition einer
  1439. DAT-Zeile zu einem Sprungbefehl sinnlos ist, weil die Anweisung DAT das
  1440. Argument B verwendet, die Anweisung "JMP" (springen) jedoch das
  1441. Argument A.  Wenn der Wert eines Befehls Unmittelbar (#) angegeben
  1442. wird, bezieht sich diese Zahl auf beide Argumente.  Die drei folgenden
  1443. Programmfragmente liefern sinnvolle Werte:
  1444.  
  1445.                DAT 8 
  1446.                ADD #1, -1 
  1447.  
  1448. Addieren von 1 zu der DAT-Anweisung hinter dem ADD-Befehl: Nach der
  1449. Ausführung enthält die Zeile "DAT 9". 
  1450.  
  1451.                DAT 15 
  1452.                DAT 6 
  1453.                SUB -1, -2 
  1454.  
  1455. "SUB -1, -2" subtrahiert von "DAT 15" den Wert 6, der in der anderen
  1456. DAT-Zeile enthalten ist.  "DAT 15" wird danach zu "DAT 9". 
  1457.  
  1458.                CMP 5, -100 
  1459.                ADD #1, -1 
  1460.  
  1461. Hier wird zur gesamten CMP-Befehlszeile oder mit anderen Worten zu
  1462. beiden Argumenten der Wert eins addiert, weil dieser unmittelbar
  1463. adressiert ist.  Anschliessend würde also die Zeile, die 6 Schritte
  1464. ($5+1$) nach CMP steht, mit der Zeile verglichen, die sich 99 ($-100+1$)
  1465. Schritte vor der CMP-Anweisung befindet.  Schliesslich noch eine
  1466. schlechte Anwendung von "ADD":
  1467.  
  1468.                DAT 10 
  1469.                JMP -30 
  1470.                ADD -2, -1 
  1471.  
  1472. Hier bezieht sich der ADD-Befehl auf die Anweisung "JMP -30" und bleibt
  1473. ohne Wirkung, weil "DAT 10" keinen sinnvollen Wert zur Addition liefern
  1474. kann: "JMP" benötigt das Argument A, "DAT" dagegen das Argument B. 
  1475.  
  1476.  
  1477.  
  1478.  
  1479. 1.11 Turniere
  1480. _____________
  1481.  
  1482.  
  1483.  
  1484. Core Wars stand im Herbst der Jahres 1986 im Rampenlicht des
  1485. Computermuseums in Boston.  Dort fand das erste internationale
  1486. Core Wars -- Turnier statt.  Von den 31 teilnehmenden Programmen
  1487. erwiesen sich drei als äusserst robust.  Sieger wurde schliesslich ein
  1488. Programm namens 'mice', in Englisch die Mehrzahl von Maus, also Mäuse. 
  1489. Der erste Preis bestand übrigens in einer Trophäe mit einer
  1490. Kernspeicher-Karte aus einem alten CDC-6600 - Computer. 
  1491.  
  1492. Das Turnier war darauf angelegt, möglichst viele Begegnungen
  1493. stattfinden zu lassen.  Aber ein vollständiger Kampf zwischen den 31
  1494. Teilnehmern, jeder gegen jeden, hätte 465 Schlachten erfordert, und
  1495. soviel Zeit stand nicht zur Verfügung.  Die Teilnehmer wurden daher
  1496. willkürlich in zwei nahezu gleich grosse Gruppen aufgeteilt.  Innerhalb
  1497. der Gruppen trat dann jeder gegen jeden an. 
  1498.  
  1499. Die vier bestplatzierten Programme von jeder Gruppe kämpften
  1500. dann wieder jedes gegen jedes.  Von diesen insgesamt acht Programmen
  1501. kamen drei ins Finale, aus dem dann der endgültige Sieger des Turniers
  1502. hervorging, eben "Mice". 
  1503.  
  1504. Dieses Siegerprogramm und ein Programm namens "Chang", das den zweiten
  1505. Platz erringen konnte, werden im dritten Kapitel vorgestellt und
  1506. erklärt.  Neu hinzugekommen ist das Kampfprogramm "Mausefalle",
  1507. welches "Mice" in den meisten Fällen schlagen kann. 
  1508.  
  1509. Im Dezember des Jahres 1988 findet übrigens wiederum ein Core Wars
  1510. Turnier statt, von dem aber die Resultate und die Siegerprogramme noch
  1511. nicht bekannt sind.
  1512.